﻿using innovations.ml.core;
using innovations.ml.core.models;
using innovations.ml.core.solvers;
using innovations.ml.data;
using MathNet.Numerics.LinearAlgebra.Double;
using MathNet.Numerics.LinearAlgebra.Generic;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.Configuration;

namespace innovations.ml.test
{
    [TestClass]
    public class CoreTestsEx3
    {        
        [TestMethod]
        public void MulticlassClassificationPrediction()
        {
            MNISTLoader mnist = new MNISTLoader();
            mnist.Load(1500);
            int numberOfLabels = 10; // digits 0 - 9
            Solver solver = new CG();
            solver.Model = new LogisticalRegressionMultiClassificationModel(mnist.X, mnist.Y, false);
            solver.Model.Lambda = 0.1;
            solver.Iterations = 50;
            solver.Run(numberOfLabels);
            Vector<double> predictions = Prediction.Predict(solver.Model.X, solver.Model.MultiClassTheta);
            double accuracy = Prediction.ComputeMean(solver.Model.Y);
            Assert.IsTrue(accuracy > .98);
        }

        [TestMethod]
        public void NeuralNetworkPrediction()
        {
            string dataPath = ConfigurationManager.AppSettings["NeuralNetworksData"].ToString();
            CSVLoader csvData = StartUp.LoadFile(dataPath);
            for (int i = 0; i < csvData.Y.Count; i++)
                csvData.Y[i] -= 1;
            string[] weightFiles = new string[2];
            weightFiles[0] = ConfigurationManager.AppSettings["NeuralNetworksWeights1"].ToString();
            weightFiles[1] = ConfigurationManager.AppSettings["NeuralNetworksWeights2"].ToString();
            CSVWeightsLoader csvWeights = StartUp.LoadWeightFile(weightFiles);
            csvData.X = csvData.X.InsertColumn(0, new DenseVector(csvData.X.RowCount, 1.0));
            Vector<double> predictions = Prediction.Predict(csvData.X, csvWeights.ThetaList);
            double accuracy = Prediction.ComputeMean(csvData.Y);
            Assert.IsTrue(accuracy > .97);
        }
    }
}
